<?php

/**
 * Author: Hancock
 * Email: 84622365@qq.com
 * Date: 8/17/2016
 * Des: 图像处理
 */
class Image
{
    protected $path;   //图片所在的路径

    /**
     * 创建图像对象时传递图像的一个路径，默认值是框架的文件上传目录
     * @param    string $path 可以指定处理图片的路径
     */
    function __construct($path = "")
    {
        if ($path == "") {
            $path = DEFAULT_UPLOAD_IMAGE_PATH;
        }
        $this->path = rtrim($path, SEPARATE) . SEPARATE;
    }

    /**
     * 对指定的图像进行缩放
     * @param    string $name 是需要处理的图片名称
     * @param    int $width 缩放后的宽度
     * @param    int $height 缩放后的高度
     * @param    string $qz 是新图片的前缀
     * @return    mixed        是缩放后的图片名称,失败返回false;
     */
    function thumb($name, $width, $height, $qz = "hk_", $hz=true)
    {
        $img_info = $this->getInfo($name);                                 //获取图片信息
        $src_img = $this->getImg($name, $img_info);                          //获取图片资源
        $size = $this->getNewSize($width, $height, $img_info);       //获取新图片尺寸
        $new_img = $this->kidOfImage($src_img, $size, $img_info);   //获取新的图片资源
        if($hz==true){
            switch ($img_info["type"]) {
                case 1:    //gif
                    $img = 'gif';
                    break;
                case 2:    //jpg
                    $img = 'jpg';
                    break;
                case 3:    //png
                    $img = 'png';
                    break;
                default:
                    return false;
                    break;
            }
            $this->thumb_origin_name = $name;
            $name = str_replace('.'.$img,'', $name).'_'.$width .'_'.$height.'.'.$img;
        }
        return $this->createNewImage($new_img, $qz . $name, $img_info);    //返回新生成的缩略图的名称，以"hk_"为前缀
    }

    /**
     * 为图片添加水印
     * @param    string $ground_name 背景图片，即需要加水印的图片，暂只支持GIF,JPG,PNG格式；
     * @param    string $water_name 图片水印，即作为水印的图片，暂只支持GIF,JPG,PNG格式;
     * @param    int $water_pos 水印位置，有10种状态，0为随机位置；
     *                    1为顶端居左，2为顶端居中，3为顶端居右；
     *                    4为中部居左，5为中部居中，6为中部居右；
     *                    7为底端居左，8为底端居中，9为底端居右；
     * @param    string $qz 加水印后的图片的文件名在原文件名前面加上这个前缀，。
     * @return    mixed            是生成水印后的图片名称,失败返回false;
     */
    function waterMark($ground_name, $water_name, $water_pos = 0, $qz = "hk_")
    {
        $cur_path = rtrim($this->path, "/") . "/";
        $dir = dirname($water_name);
        if ($dir == ".") {
            $wpath = $cur_path;
        } else {
            $wpath = $dir . "/";
            $water_name = basename($water_name);

        }


        if (file_exists($cur_path . $ground_name) && file_exists($wpath . $water_name)) {
            $ground_info = $this->getInfo($ground_name);               //获取背景信息
            $water_info = $this->getInfo($water_name);                 //获取水印图片信息

            if (!$pos = $this->position($ground_info, $water_info, $water_pos)) {
                LD("<font color='red'>水印不应该比背景图片小！</font>");
                return false;
            }

            $ground_img = $this->getImg($ground_name, $ground_info);    //获取背景图像资源
            $water_img = $this->getImg($water_name, $water_info);       //获取水印图片资源

            $ground_img = $this->copyImage($ground_img, $water_img, $pos, $water_info);  //拷贝图像

            return $this->createNewImage($ground_img, $qz . $ground_name, $ground_info);

        } else {
            LD("<font color='red'>图片或水印图片不存在！</font>");
            return false;
        }
    }

    private function position($ground_info, $water_info, $water_pos)
    {
        //需要加水印的图片的长度或宽度比水印还小，无法生成水印！
        if (($ground_info["width"] < $water_info["width"]) || ($ground_info["height"] < $water_info["height"])) {
            return false;
        }
        switch ($water_pos) {
            case 1://1为顶端居左
                $pos_x = 0;
                $pos_y = 0;
                break;
            case 2://2为顶端居中
                $pos_x = ($ground_info["width"] - $water_info["width"]) / 2;
                $pos_y = 0;
                break;
            case 3://3为顶端居右
                $pos_x = $ground_info["width"] - $water_info["width"];
                $pos_y = 0;
                break;
            case 4://4为中部居左
                $pos_x = 0;
                $pos_y = ($ground_info["height"] - $water_info["height"]) / 2;
                break;
            case 5://5为中部居中
                $pos_x = ($ground_info["width"] - $water_info["width"]) / 2;
                $pos_y = ($ground_info["height"] - $water_info["height"]) / 2;
                break;
            case 6://6为中部居右
                $pos_x = $ground_info["width"] - $water_info["width"];
                $pos_y = ($ground_info["height"] - $water_info["height"]) / 2;
                break;
            case 7://7为底端居左
                $pos_x = 0;
                $pos_y = $ground_info["height"] - $water_info["height"];
                break;
            case 8://8为底端居中
                $pos_x = ($ground_info["width"] - $water_info["width"]) / 2;
                $pos_y = $ground_info["height"] - $water_info["height"];
                break;
            case 9://9为底端居右
                $pos_x = $ground_info["width"] - $water_info["width"];
                $pos_y = $ground_info["height"] - $water_info["height"];
                break;
            case 0:
            default://随机
                $pos_x = rand(0, ($ground_info["width"] - $water_info["width"]));
                $pos_y = rand(0, ($ground_info["height"] - $water_info["height"]));
                break;
        }

        return array("pos_x" => $pos_x, "pos_y" => $pos_y);
    }

    // 获取图片的信息
    private function getInfo($name)
    {
        $data = getimagesize($this->path . $name);
        $img_info["width"] = $data[0];
        $img_info["height"] = $data[1];
        $img_info["type"] = $data[2];
        return $img_info;
    }

    // 创建图像资源
    private function getImg($name, $img_info)
    {
        $src_pic = $this->path . $name;
        switch ($img_info["type"]) {
            case 1:    //gif
                $img = imagecreatefromgif($src_pic);
                break;
            case 2:    //jpg
                $img = imagecreatefromjpeg($src_pic);
                break;
            case 3:    //png
                $img = imagecreatefrompng($src_pic);
                break;
            default:
                return false;
                break;
        }
        return $img;
    }

    //返回等比例缩放的图片宽度和高度，如果原图比缩放后的还小保持不变
    private function getNewSize($width, $height, $img_info)
    {
        $size = [];
        $size["width"] = $img_info["width"];          //将原图片的宽度给数组中的$size["width"]
        $size["height"] = $img_info["height"];        //将原图片的高度给数组中的$size["height"]

        if ($width < $img_info["width"]) {
            $size["width"] = $width;             //缩放的宽度如果比原图小才重新设置宽度
        }

        if ($height < $img_info["height"]) {
            $size["height"] = $height;            //缩放的高度如果比原图小才重新设置高度
        }

        if ($img_info["width"] * $size["width"] > $img_info["height"] * $size["height"]) {
            $size["height"] = round($img_info["height"] * $size["width"] / $img_info["width"]);
        } else {
            $size["width"] = round($img_info["width"] * $size["height"] / $img_info["height"]);
        }

        return $size;
    }

    private function kidOfImage($src_img, $size, $img_info)
    {
        $new_img = imagecreatetruecolor($size["width"], $size["height"]);
        $otsc = imagecolortransparent($src_img); //将某个颜色定义为透明色
        if ($otsc >= 0 && $otsc < imagecolorstotal($src_img)) {  //取得一幅图像的调色板中颜色的数目
            $transparentcolor = imagecolorsforindex($src_img, $otsc); //取得某索引的颜色
            $newtransparentcolor = imagecolorallocate(
                $new_img,
                $transparentcolor['red'],
                $transparentcolor['green'],
                $transparentcolor['blue']
            );

            imagefill($new_img, 0, 0, $newtransparentcolor);
            imagecolortransparent($new_img, $newtransparentcolor);
        }
        imagecopyresized($new_img, $src_img, 0, 0, 0, 0, $size["width"], $size["height"], $img_info["width"], $img_info["height"]);
        imagedestroy($src_img);
        return $new_img;
    }

    private function createNewImage($new_img, $new_name, $img_info)
    {
        $result = false;
        $this->path = rtrim($this->path, "/") . "/";
        switch ($img_info["type"]) {
            case 1:    //gif
                $result = imagegif($new_img, $this->path . $new_name);
                break;
            case 2:    //jpg
                $result = imagejpeg($new_img, $this->path . $new_name);
                break;
            case 3:    //png
                $result = imagepng($new_img, $this->path . $new_name);
                break;
        }
        if ($result === false) {
            return false;
        }
        imagedestroy($new_img);
        return $new_name;
    }

    private function copyImage($ground_img, $water_img, $pos, $water_info)
    {
        imagecopy($ground_img, $water_img, $pos["posX"], $pos["posY"], 0, 0, $water_info["width"], $water_info["height"]);
        imagedestroy($water_img);
        return $ground_img;
    }

    public function getThumbOriginName(){
        return $this->thumb_origin_name;
    }
}
